/*
 * Copyright 2011 The Apache Software Foundation.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package fr.gaellalire.jzip.view;

import java.awt.BorderLayout;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DragGestureEvent;
import java.awt.dnd.DragGestureListener;
import java.awt.dnd.DragSource;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.io.File;
import java.io.IOException;
import java.util.zip.ZipException;

import javax.swing.DefaultListSelectionModel;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.TransferHandler;

import fr.gaellalire.jzip.model.ZipTableModel;

/**
 *
 * @author Gael Lalire
 */
public class ContentPanel extends JPanel {

    private static final long serialVersionUID = 386780443754858010L;

    private JTable table;

    private ZipTableModel dm;

    public ZipTableModel getDm() {
        return dm;
    }

    private JTextField locationTextField;

    public ContentPanel(final File file) {
        setLayout(new BorderLayout());
        JPanel location = new JPanel(new BorderLayout());
        locationTextField = new JTextField("/");
        locationTextField.setEditable(false);
        location.add(locationTextField);
        JButton parentButton = new JButton("Parent");
        parentButton.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(final ActionEvent e) {
                goParent();
            }
        });
        location.add(parentButton, BorderLayout.WEST);
        add(location, BorderLayout.NORTH);

        NameTableCellRenderer renderer = new NameTableCellRenderer();
        try {
            dm = new ZipTableModel(file);
            table = new JTable(dm);
            table.setDefaultRenderer(JLabel.class, renderer);
            table.setDefaultRenderer(Long.class, new NoBackgroundTableCellRenderer());
            table.setSelectionModel(new DefaultListSelectionModel());
            TransferHandler newHandler = new TransferHandler() {

                private static final long serialVersionUID = -1762010579879732310L;

                @Override
                public int getSourceActions(final JComponent c) {
                    return COPY;
                }

            };
            table.setTransferHandler(newHandler);
            table.setDragEnabled(true);

            table.addMouseListener(new MouseAdapter() {
                @Override
                public void mouseClicked(final MouseEvent e) {
                    if (e.getClickCount() == 2) {
                        goExplore();
                    }
                }
            });

            DragSource source = DragSource.getDefaultDragSource();
            source.createDefaultDragGestureRecognizer(table, DnDConstants.ACTION_COPY, new DragGestureListener() {

                @Override
                public void dragGestureRecognized(final DragGestureEvent dge) {
                    // grab the selected files from the table model

                    Transferable transferable = new Transferable() {

                        @Override
                        public boolean isDataFlavorSupported(final DataFlavor flavor) {
                            return flavor.equals(DataFlavor.javaFileListFlavor);
                        }

                        @Override
                        public DataFlavor[] getTransferDataFlavors() {
                            return new DataFlavor[] { DataFlavor.javaFileListFlavor };
                        }

                        @Override
                        public Object getTransferData(final DataFlavor flavor) throws UnsupportedFlavorException, IOException {
                            int[] selectedRows = table.getSelectedRows();
                            int[] modelSelectedRows = new int[selectedRows.length];
                            for (int i = 0; i < selectedRows.length; i++) {
                                modelSelectedRows[i] = table.convertRowIndexToModel(selectedRows[i]);
                            }
                            return dm.createFiles(modelSelectedRows);
                        }
                    };

                    // and this is the magic right here
                    dge.startDrag(null, transferable);
                }
            });

            table.setDefaultEditor(JLabel.class, renderer);
            table.setAutoCreateRowSorter(true);
            table.getColumnModel().getColumn(0).setPreferredWidth(400);
            table.setRowHeight(22);
            JScrollPane scrollPane = new JScrollPane(table);
            add(scrollPane);
        } catch (ZipException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public void goParent() {
        dm.goParent();
        locationTextField.setText(dm.getLocation());
    }

    public void selectAll() {
        table.selectAll();
    }

    public void goExplore() {
        if (table.getSelectedRowCount() == 1) {
            try {
                dm.select(table.convertRowIndexToModel(table.getSelectedRow()));
            } catch (IOException e) {
                JOptionPane.showMessageDialog(this, "Unable to open file, the file is corrupted", "Unable to open file", JOptionPane.ERROR_MESSAGE);
            }
            locationTextField.setText(dm.getLocation());
        }
    }

    public void focusTable() {
        table.requestFocusInWindow();
    }

    public void dispose() {
        dm.dispose();
    }

    public void rebuild() throws IOException {
        dm.rebuild();
    }

}
